home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 10 / AACD 10.iso / AACD / Online / SpeakFreely / src / lpc10 / placev.c < prev    next >
C/C++ Source or Header  |  2000-05-18  |  5KB  |  157 lines

  1. /*******************************************************************
  2. *
  3. *    PLACEV Version 48
  4. *
  5. *******************************************************************/
  6.  
  7. #include "lpcdefs.h"
  8. #include "config.ch"
  9.  
  10. placev( osbuf, osptr, obound, vwin)
  11. int osbuf[], osptr, *obound, vwin[2][AF];
  12. {
  13.  
  14. /*   Arguments
  15. *    OSBUF    Buffer which holds sorted indexes of onsets
  16. *    OSPTR    Free pointer into OSBUF
  17. *    VWIN    Buffer of Voicing Window Positions (Modified)
  18. *    OBOUND    This variable is set by this procedure and used
  19. *        in placing analysis windows (PLACEA).  Bit 1
  20. *        indicates whether an onset bounds the left side
  21. *        of the voicing window, and bit 2 indicates whether
  22. *        an onset bounds the right side of the voicing window.
  23. *   Variables
  24. *    LRANGE, HRANGE  Range in which window is placed
  25. *    OSPTR1     OSPTR excluding samaples in 3F
  26. */
  27.  
  28. int lrange, hrange, i;
  29. int q;
  30. int osptr1;
  31. short crit;
  32.  
  33. /*   Voicing Window Placement
  34. *
  35. *         __________________ __________________ ______________
  36. *        |                  |                  |
  37. *        |        1F        |        2F        |        3F ...
  38. *        |__________________|__________________|______________
  39. *
  40. *    Previous |
  41. *      Window |
  42. *  ...________|
  43. *
  44. *             |                                |
  45. *      ------>| This window's placement range  |<------
  46. *             |                                |
  47. *
  48. *   There are three cases.  Note that these are different from those
  49. *   given in the LPC-10e phase 1 report.
  50. *
  51. *   1.  If there are no onsets in this range, then the voicing window
  52. *   is centered in the pitch window.  If such a placement is not within
  53. *   the window's placement range, then the window is placed in the left-
  54. *   most portion of the placement range.  Its length is always MAXWIN.
  55. *
  56. *   2.  If the first onset is in 2F and there is sufficient room to place
  57. *   the window immediately before this onset, then the window is placed
  58. *   there, and its length is set to the maximum possible under these
  59. *   constraints.
  60. *
  61. *    "Critical Region Exception":  If there is another onset in 2F
  62. *    such that a window can be placed between the two onsets, the
  63. *    window is placed there (ie, as in case 3).
  64. *
  65. *   3.  Otherwise, the window is placed immediately AFter the onset.  The 
  66. *   window's length
  67. *   is the longest length that can fit in the range under these constraints,
  68. *   except that the window may be shortened even further to avoid overlapping
  69. *   other onsets in the placement range.  In any case, the window's length
  70. *   is at least MINWIN.
  71. *
  72. *   Note that the values of MINWIN and LFRAME must be chosen such
  73. *   that case 2 = false implies case 3 = true.   This means that
  74. *   MINWIN <= LFRAME/2.  If this were not the case, then a fourth case
  75. *   would have to be added for when the window cannot fit either before
  76. *   or AFter the onset.
  77. *
  78. *   Note also that onsets which weren't in 2F last time may be in 1F this
  79. *   time, due to the filter delays in computing onsets.  The result is that
  80. *   occasionally a voicing window will overlap that onset.  The only way
  81. *   to circumvent this problem is to add more delay in processing input
  82. *   speech.  In the trade-off between delay and window-placement, window
  83. *   placement lost.
  84. */
  85.  
  86. /* Compute the placement range    */
  87.  
  88.  
  89. lrange = mmax(vwin[1][AF-2]+1, (AF-2)*LFRAME+1);
  90. hrange = AF*LFRAME;
  91.  
  92. /* Compute OSPTR1, so the following code only looks at relevant onsets.    */
  93.  
  94. for (osptr1=osptr-1; osptr1>=1; osptr1--) {
  95.    if (osbuf[osptr1-1] <= hrange) break;
  96. }
  97. osptr1++;
  98.  
  99. /* Check for case 1 first (fast case):    */
  100.  
  101. if ((osptr1 <= 1) || (osbuf[osptr1-2] < lrange)) {
  102.     vwin[0][AF-1] = mmax(vwin[1][AF-2]+1, DVWINL);
  103.     vwin[1][AF-1] = vwin[0][AF-1] + MAXWIN - 1;
  104.     *obound = 0;
  105. }
  106. else {
  107.  
  108. /* Search backward in OSBUF for first onset in range.
  109. * This code relies on the above check being performed first.    */
  110.  
  111.     for(q=osptr1-1;q>=1;q--) {
  112.         if (osbuf[q-1] < lrange) break;
  113.     }
  114.     q++;
  115.  
  116. /* Check for case 2 (placement before onset):
  117.  
  118. * Check for critical region exception:    */
  119.     
  120.     crit = 0;
  121.     for(i=q+1;i<=osptr1-1;i++) {
  122.         if (osbuf[i-1] - osbuf[q-1] >= MINWIN) {
  123.             crit = 1;
  124.             break;
  125.         }
  126.     }
  127.  
  128.     if (!crit && osbuf[q-1] > mmax((AF-1)*LFRAME, lrange+MINWIN-1)) {
  129.         vwin[1][AF-1] = osbuf[q-1] - 1;
  130.         vwin[0][AF-1] = mmax (lrange, vwin[1][AF-1]-MAXWIN+1);
  131.         *obound = 2;
  132.     }
  133. /* Case 3 (placement AFter onset)    */
  134.     
  135.     else {
  136.         vwin[0][AF-1] = osbuf[q-1];
  137. L110:        q++;
  138.         if(q < osptr1) {
  139.             if(osbuf[q-1] <= vwin[0][AF-1] + MAXWIN) {
  140.                 if (osbuf[q-1]  < vwin[0][AF-1] + MINWIN) goto L110;
  141.                 vwin[1][AF-1] = osbuf[q-1] - 1;
  142.                 *obound = 3;
  143.             }
  144.             else {
  145.                 vwin[1][AF-1] = mmin(vwin[0][AF-1] + MAXWIN - 1, hrange);
  146.                 *obound = 1;
  147.             }
  148.         }
  149.         else {
  150.             vwin[1][AF-1] = mmin(vwin[0][AF-1] + MAXWIN - 1, hrange);
  151.             *obound = 1;
  152.         }
  153.     }
  154.  
  155. }
  156. }
  157.